---
sidebar_position: 3
---

import azureLogo from '/img/azureLogo.png';
import hljsLogo from '/img/hljsLogo.png';
import WebModelLogo from '/img/chip.svg';

# External Modules

To keep Deep Chat as lightweight as possible, some of its functionality requires the use of external modules.
The component has been set up to recognise them by using the `window` object:

| Functionality                                                                       | Module                                                                                                                                                                                                          | Window             |
| ----------------------------------------------------------------------------------- | --------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- | ------------------ |
| Higlighting [code](/docs/messages#code-messages)                                    | <img src={hljsLogo} width="20" style={{float: 'left', marginRight: '8px', marginTop: '4px'}} /> [highlight.js](https://www.npmjs.com/package/highlight.js?activeTab=readme)                                     | `window.hljs`      |
| [Speech to text](/docs/speech#speechToText) with [Azure](/docs/speech#AzureOptions) | <img src={azureLogo} width="20" style={{float: 'left', marginRight: '7px', marginTop: '5px'}} /> [microsoft-cognitiveservices-speech-sdk](https://www.npmjs.com/package/microsoft-cognitiveservices-speech-sdk) | `window.SpeechSDK` |
| LLM [web model](/docs/webModel#webModel)                                            | <WebModelLogo width="18" style={{float: 'left', marginRight: '6px', marginTop: '4.5px'}} className="adaptive-logo-filter"/>[deep-chat-web-llm](https://github.com/OvidijusParsiunas/web-llm)                    | `window.webLLM`    |

## Implementation

Here are some simple approaches you can use to add these modules to your project:

- <b>Import from a dependancy</b> <br />
  If you are using a dependancy manager such as npm, you can import the modules and assign them to window:

  <br />
  <br />

  | Module                                                                            | URL                                                                                            |
  | --------------------------------------------------------------------------------- | ---------------------------------------------------------------------------------------------- |
  | [highlight](https://www.npmjs.com/package/highlight.js?activeTab=readme)          | import hljs from "highlight.js"; <br /> window.hljs = hljs;                                    |
  | [speech](https://www.npmjs.com/package/microsoft-cognitiveservices-speech-sdk)    | import \* as sdk from 'microsoft-cognitiveservices-speech-sdk'; <br /> window.SpeechSDK = sdk; |
  | [web model](https://www.npmjs.com/package/microsoft-cognitiveservices-speech-sdk) | import \* as webLLM from 'deep-chat-web-llm' <br /> window.webLLM = webLLM;                    |

  <br />

- <b>Dynamic import from a dependancy (recommended for SSR)</b> <br />
  If you are using a dependancy manager such as npm, you can dynamically import the modules and assign them to the window
  object. The highlightjs module can load after messages are generated, use the refreshMessages method to apply it:

  <br />
  <br />

  | Module                                                                         | URL                                                                                                                                                                                                                              |
  | ------------------------------------------------------------------------------ | -------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
  | [highlight](https://www.npmjs.com/package/highlight.js?activeTab=readme)       | import("highlight.js").then((module) => \{ <br /> &nbsp;&nbsp;&nbsp;&nbsp; window.hljs = module.default; <br /> &nbsp;&nbsp;&nbsp;&nbsp; chatElementRef.current?.[refreshMessages](/docs/methods#refreshMessages)(); <br /> \}); |
  | [speech](https://www.npmjs.com/package/microsoft-cognitiveservices-speech-sdk) | import('microsoft-cognitiveservices-speech-sdk').then((module) => \{ <br /> &nbsp;&nbsp;&nbsp;&nbsp; window.SpeechSDK = module; <br /> \});                                                                                      |
  | [web model](https://github.com/OvidijusParsiunas/web-llm)                      | import('deep-chat-web-llm').then((module) => \{ <br /> &nbsp;&nbsp;&nbsp;&nbsp; window.webLLM = module; <br /> \});                                                                                                              |

  <br />

- <b>Script from a CDN</b> <br />
  You can create script tags with the following URLs and append them to the document body (or manually add the scripts to
  your markup). The highlightjs module can load after messages are generated, use the refreshMessages method to apply it
  (window object is automatically populated).

  <br />
  <br />

  | Module                                                                         | URL                                                                                                                                                                                                                                                                                                    |
  | ------------------------------------------------------------------------------ | ------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------ |
  | [highlight](https://www.npmjs.com/package/highlight.js?activeTab=readme)       | const script = document.createElement('script'); <br /> script.src = 'https://cdnjs.cloudflare.com/ajax/libs/highlight.js/11.8.0/highlight.min.js'; <br /> script.onload = () => chatElementRef.current?.[refreshMessages](/docs/methods#refreshMessages)(); <br /> document.body.appendChild(script); |
  | [speech](https://www.npmjs.com/package/microsoft-cognitiveservices-speech-sdk) | const script = document.createElement('script'); <br /> script.src = 'https://aka.ms/csspeech/jsbrowserpackageraw'; <br /> document.body.appendChild(script);                                                                                                                                          |
  | [web model](https://github.com/OvidijusParsiunas/web-llm)                      | const script = document.createElement('script'); <br /> script.src = 'https://cdn.jsdelivr.net/gh/OvidijusParsiunas/web-llm/lib/index.js'; <br /> document.body.appendChild(script);                                                                                                                   |

  <br />

- <b>Script from within the project</b> <br />
  You can manually download the files from the URLs above, add them to the script tags and append them to the document body
  (or manually add the scripts to your markup). The highlightjs module can load after messages are generated, use the
  refreshMessages method to apply it (window object is automatically populated).

  <br />
  <br />

  | Module                                                                   | URL                                                                                                                                                                                                                                         |
  | ------------------------------------------------------------------------ | ------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
  | [highlight](https://www.npmjs.com/package/highlight.js?activeTab=readme) | const script = document.createElement('script'); <br /> script.src = 'highlight.min.js'; <br /> script.onload = () => chatElementRef.current?.[refreshMessages](/docs/methods#refreshMessages)(); <br /> document.body.appendChild(script); |
  | any other                                                                | const script = document.createElement('script'); <br /> script.src = 'name.js'; <br /> document.body.appendChild(script);                                                                                                                   |

  <br />

If your project is using `TypeScript`, add this to the file where the modules are being used:

```
import hljs from 'highlight.js';
import * as sdk from 'microsoft-cognitiveservices-speech-sdk';
import * as webLLM from 'deep-chat-web-llm';

declare global {
  interface Window {
    hljs: typeof hljs;
    SpeechSDK: typeof sdk;
    webLLM: typeof webLLM;
  }
}
```

## Examples

React project that uses a package bundler - should work similarly for other [Frameworks](/examples/frameworks):

[Click for Live Example](https://codesandbox.io/p/devbox/agitated-edison-9y3yh9?layout=%257B%2522sidebarPanel%2522%253A%2522EXPLORER%2522%252C%2522rootPanelGroup%2522%253A%257B%2522direction%2522%253A%2522horizontal%2522%252C%2522contentType%2522%253A%2522UNKNOWN%2522%252C%2522type%2522%253A%2522PANEL_GROUP%2522%252C%2522id%2522%253A%2522ROOT_LAYOUT%2522%252C%2522panels%2522%253A%255B%257B%2522type%2522%253A%2522PANEL_GROUP%2522%252C%2522contentType%2522%253A%2522UNKNOWN%2522%252C%2522direction%2522%253A%2522vertical%2522%252C%2522id%2522%253A%2522clq1fm83w00073b6hg3whvh9p%2522%252C%2522sizes%2522%253A%255B70%252C30%255D%252C%2522panels%2522%253A%255B%257B%2522type%2522%253A%2522PANEL_GROUP%2522%252C%2522contentType%2522%253A%2522EDITOR%2522%252C%2522direction%2522%253A%2522horizontal%2522%252C%2522id%2522%253A%2522EDITOR%2522%252C%2522panels%2522%253A%255B%257B%2522type%2522%253A%2522PANEL%2522%252C%2522contentType%2522%253A%2522EDITOR%2522%252C%2522id%2522%253A%2522clq1fm83v00023b6hggc9e0ye%2522%257D%255D%257D%252C%257B%2522type%2522%253A%2522PANEL_GROUP%2522%252C%2522contentType%2522%253A%2522SHELLS%2522%252C%2522direction%2522%253A%2522horizontal%2522%252C%2522id%2522%253A%2522SHELLS%2522%252C%2522panels%2522%253A%255B%257B%2522type%2522%253A%2522PANEL%2522%252C%2522contentType%2522%253A%2522SHELLS%2522%252C%2522id%2522%253A%2522clq1fm83v00043b6hbxrmzcf7%2522%257D%255D%252C%2522sizes%2522%253A%255B100%255D%257D%255D%257D%252C%257B%2522type%2522%253A%2522PANEL_GROUP%2522%252C%2522contentType%2522%253A%2522DEVTOOLS%2522%252C%2522direction%2522%253A%2522vertical%2522%252C%2522id%2522%253A%2522DEVTOOLS%2522%252C%2522panels%2522%253A%255B%257B%2522type%2522%253A%2522PANEL%2522%252C%2522contentType%2522%253A%2522DEVTOOLS%2522%252C%2522id%2522%253A%2522clq1fm83v00063b6hiy17w0ip%2522%257D%255D%252C%2522sizes%2522%253A%255B100%255D%257D%255D%252C%2522sizes%2522%253A%255B62.45764825392191%252C37.54235174607809%255D%257D%252C%2522tabbedPanels%2522%253A%257B%2522clq1fm83v00023b6hggc9e0ye%2522%253A%257B%2522id%2522%253A%2522clq1fm83v00023b6hggc9e0ye%2522%252C%2522tabs%2522%253A%255B%255D%257D%252C%2522clq1fm83v00063b6hiy17w0ip%2522%253A%257B%2522id%2522%253A%2522clq1fm83v00063b6hiy17w0ip%2522%252C%2522tabs%2522%253A%255B%257B%2522id%2522%253A%2522clq1fm83v00053b6h2vei3mas%2522%252C%2522mode%2522%253A%2522permanent%2522%252C%2522type%2522%253A%2522TASK_PORT%2522%252C%2522taskId%2522%253A%2522dev%2522%252C%2522port%2522%253A5173%252C%2522path%2522%253A%2522%252F%2522%257D%252C%257B%2522type%2522%253A%2522SANDBOX_INFO%2522%252C%2522id%2522%253A%2522clq1gf1mq02yk3b6h7u2qo17i%2522%252C%2522mode%2522%253A%2522permanent%2522%257D%255D%252C%2522activeTabId%2522%253A%2522clq1fm83v00053b6h2vei3mas%2522%257D%252C%2522clq1fm83v00043b6hbxrmzcf7%2522%253A%257B%2522id%2522%253A%2522clq1fm83v00043b6hbxrmzcf7%2522%252C%2522tabs%2522%253A%255B%257B%2522id%2522%253A%2522clq1fm83v00033b6hcx2dya5e%2522%252C%2522mode%2522%253A%2522permanent%2522%252C%2522type%2522%253A%2522TASK_LOG%2522%252C%2522taskId%2522%253A%2522dev%2522%257D%255D%252C%2522activeTabId%2522%253A%2522clq1fm83v00033b6hcx2dya5e%2522%257D%257D%252C%2522showDevtools%2522%253Atrue%252C%2522showShells%2522%253Atrue%252C%2522showSidebar%2522%253Atrue%252C%2522sidebarPanelSize%2522%253A15%257D)

VanillaJS approach with no bundler (this can also be used as fallback if above doesn't work):

[Click for Live Example](https://codesandbox.io/s/deep-chat-vanillajs-external-modules-fgw5k5?file=/index.html)

## Explanation

The decision to have developers download external dependancies was not easily made and there were multiple reasons that
lead us down this path. <br />
First, the post-compression size of the above modules is orders of magnitude bigger than Deep Chat. This
ruled out the idea of pre-bundling them into the component. <br />
We then spent some time experimenting with [dynamic imports](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Operators/import) which
seemed promising, but unfortunatelly we hit a roadblock that had no simple way of overcoming; Deep Chat itself is an injectable component that
exists as part of a parent project which can use any type of a bundler to compile it. This is where
[dynamic imports](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Operators/import) become
problematic as they are not supported by all bundlers and in many cases need extra configuration to work. <br />
Therefore, to make the lives of our developers as simple as possible; for use cases that do not need the extra functionality - Deep Chat can
be installed without any extra work, for use cases that do - we leave the decision of how to implement the modules
in their hands to alllow them to tailor the approach for their project.

## Troubleshooting

If you are experiencing issues for importing/exporting files, please see [**github issues**](https://github.com/OvidijusParsiunas/deep-chat/issues) or create
a [**new issue ticket**](https://github.com/OvidijusParsiunas/deep-chat/issues/new) and we will look into
it as soon as possible.
